﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Xunit;

namespace Windy.Transformations.Test.Samples
{
    public class FibonacciLSystem
    {
        /*
        http://en.wikipedia.org/wiki/Fibonacci_sequence
        Fibonacci
         
        If we define the following simple grammar:
        variables : A B
        constants : none
        start  : A
        rules  : (A → B), (B → AB)
        then this L-system produces the following sequence of strings:
        n = 0 : A
        n = 1 : B
        n = 2 : AB
        n = 3 : BAB
        n = 4 : ABBAB
        n = 5 : BABABBAB
        n = 6 : ABBABBABABBAB
        n = 7 : BABABBABABBABBABABBAB
        */
        [Fact()]
        public void FibonacciSequence()
        {
            var fibonacciRuleSet = new Transformation<char, char, char>(
                           (c) => c,
                           new ExpandTransformRule<char, char, char>('B', "AB"),
                           new ReplaceTransformRule<char, char, char>('A', 'B'),
                           new BlockTransformRule<char>() // Works as a protector that eliminate the unregistered items 
                           );

            string[] statusList = new string[]
            {
                "A",
                "B",
                "AB",
                "BAB",
                "ABBAB",
                "BABABBAB",
                "ABBABBABABBAB",
                "BABABBABABBABBABABBAB",
            };

            var current = new List<char>(statusList[0]);

            for (int fo = 1; fo < statusList.Length; fo++)
            {
                fibonacciRuleSet.ApplyToList(current);
                var currentString = new string(current.ToArray());

                Assert.Equal(statusList[fo], currentString);
            }
        }
    }
}
